url = function(host, scheme='http', user=NULL, password=NULL, port=NULL, path='', query=NULL, fragment=NULL) {
   object = list(host=host, scheme=scheme, user=user, password=password, port=port, path=path, query=query, fragment=fragment, url=NULL)
   if (!is.null(user)) user = paste(c(user, password), collapse=':')
   host = paste(c(host, port), collapse=':')
   authority = sprintf('://%s/', paste(c(user, host), collapse='@'))
   path = gsub('^/+|/+$', '', path)
   query = 
      if (!is.null(query)) sprintf('?%s', query)
      else ''
   fragment = 
      if (!is.null(fragment)) sprintf('#%s', fragment)
      else ''
   object$url = paste(scheme, authority, path, query, fragment, sep='')
   class(object) = c('url', class(object))
   return(object) }
   
local({
   functions = list(
      str.url=function(url) url$url,
      print.url=function(url) print(str(url)))
   for (name in names(functions))
      assign(name, functions[[name]], env=globalenv()) })
